home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 4 / Apprentice-Release4.iso / Languages / PowerMacOberon 1.2 / Debugger / Debug.Text (.txt) < prev    next >
Oberon Text  |  1995-08-18  |  197KB  |  1,393 lines

  1. Times12.Scn.Fnt
  2. StyleElems
  3. Alloc
  4. Header
  5. Times14b.Scn.Fnt
  6. Syntax10.Scn.Fnt
  7. HeaderEnd
  8. Standard
  9. Standard
  10. ParcElems
  11. Alloc
  12. Times18b.Scn.Fnt
  13. HeaderEnd
  14. Standard
  15. HeaderEnd
  16. Times12i.Scn.Fnt
  17. Standard
  18. Standard
  19. Standard
  20. Standard
  21. Standard
  22. Standard
  23. HeaderEnd
  24. Header2
  25. Times12b.Scn.Fnt
  26. Header2End
  27. Palatino10.Scn.Fnt
  28. Palatino10b.Scn.Fnt
  29. AfterFigure
  30. Standard
  31. PictElems
  32. Alloc
  33. dddddd
  34. ff33@
  35. ffffff
  36. ffff33
  37. ff33ff
  38. ff3333
  39. 33ffff
  40. 33ff33
  41. 3333ff
  42. 333333
  43. wwwwww
  44. UUUUUU
  45. DDDDDD
  46. """"""
  47. AfterFigure
  48. dddddd
  49. ff33@
  50. ffffff
  51. ffff33
  52. ff33ff
  53. ff3333
  54. 33ffff
  55. 33ff33
  56. 3333ff
  57. 333333
  58. wwwwww
  59. UUUUUU
  60. DDDDDD
  61. """"""
  62. AfterFigure
  63. dddddd
  64. ff33@
  65. ffffff
  66. ffff33
  67. ff33ff
  68. ff3333
  69. 33ffff
  70. 33ff33
  71. 3333ff
  72. 333333
  73. wwwwww
  74. UUUUUU
  75. DDDDDD
  76. """"""
  77. dddddd
  78. ff33@
  79. ffffff
  80. ffff33
  81. ff33ff
  82. ff3333
  83. 33ffff
  84. 33ff33
  85. 3333ff
  86. 333333
  87. wwwwww
  88. UUUUUU
  89. DDDDDD
  90. """"""
  91. Standard
  92. dddddd
  93. ff33@
  94. ffffff
  95. ffff33
  96. ff33ff
  97. ff3333
  98. 33ffff
  99. 33ff33
  100. 3333ff
  101. 333333
  102. wwwwww
  103. UUUUUU
  104. DDDDDD
  105. """"""
  106. dddddd
  107. ff33@
  108. ffffff
  109. ffff33
  110. ff33ff
  111. ff3333
  112. 33ffff
  113. 33ff33
  114. 3333ff
  115. 333333
  116. wwwwww
  117. UUUUUU
  118. DDDDDD
  119. """"""
  120. dddddd
  121. ff33@
  122. ffffff
  123. ffff33
  124. ff33ff
  125. ff3333
  126. 33ffff
  127. 33ff33
  128. 3333ff
  129. 333333
  130. wwwwww
  131. UUUUUU
  132. DDDDDD
  133. """"""
  134. dddddd
  135. ff33@
  136. ffffff
  137. ffff33
  138. ff33ff
  139. ff3333
  140. 33ffff
  141. 33ff33
  142. 3333ff
  143. 333333
  144. wwwwww
  145. UUUUUU
  146. DDDDDD
  147. """"""
  148.     Geneva12.Scn.Fnt
  149. Standard
  150. ff33ff@
  151. ff33@
  152. dddddd
  153. ffff@
  154. 33ff33@
  155. 3333@
  156. """"""@
  157. 33ffff@
  158. 33ff@
  159. DDDDDD@
  160. ffff33@
  161. wwwwww@
  162. ffffff@
  163. 3333@
  164. 33ff@
  165. ffff@
  166. 3333@
  167. 33ff@
  168. 3333@
  169. ff33@
  170. 33ff@
  171. 333333@
  172. ffff@
  173. 3333ff@
  174. ff33@
  175. ff3333@
  176. ffff@
  177. Header2
  178. Header2End
  179. Header3
  180. Header3
  181. ??????
  182. VVVVVV
  183. dddddd 
  184. xxppkk
  185. ZZSSWW
  186. %%$$JJ
  187. ))%%oo
  188. mmmmmm
  189. 33ffff
  190. 33ff33
  191. 3333ff
  192. 333333
  193. dddddd 
  194. wwwwww
  195. UUUUUU
  196. DDDDDD
  197. """"""@
  198. Standard
  199. Header2End
  200. Standard
  201. Standard
  202. dddddd
  203. ff33@
  204. ffffff
  205. ffff33
  206. ff33ff
  207. ff3333
  208. 33ffff
  209. 33ff33
  210. 3333ff
  211. 333333
  212. wwwwww
  213. UUUUUU
  214. DDDDDD
  215. """"""
  216. dddddd
  217. ff33@
  218. ffffff
  219. ffff33
  220. ff33ff
  221. ff3333
  222. 33ffff
  223. 33ff33
  224. 3333ff
  225. 333333
  226. wwwwww
  227. UUUUUU
  228. DDDDDD
  229. """"""
  230. dddddd
  231. ff33@
  232. ffffff
  233. ffff33
  234. ff33ff
  235. ff3333
  236. 33ffff
  237. 33ff33
  238. 3333ff
  239. 333333
  240. wwwwww
  241. UUUUUU
  242. DDDDDD
  243. """"""
  244. dddddd
  245. ff33@
  246. ffffff
  247. ffff33
  248. ff33ff
  249. ff3333
  250. 33ffff
  251. 33ff33
  252. 3333ff
  253. 333333
  254. wwwwww
  255. UUUUUU
  256. DDDDDD
  257. """"""
  258. dddddd
  259. ff33@
  260. ffffff
  261. ffff33
  262. ff33ff
  263. ff3333
  264. 33ffff
  265. 33ff33
  266. 3333ff
  267. 333333
  268. wwwwww
  269. UUUUUU
  270. DDDDDD
  271. """"""
  272. dddddd
  273. ff33@
  274. ffffff
  275. ffff33
  276. ff33ff
  277. ff3333
  278. 33ffff
  279. 33ff33
  280. 3333ff
  281. 333333
  282. wwwwww
  283. UUUUUU
  284. DDDDDD
  285. """"""
  286. Standard
  287. dddddd
  288. ff33@
  289. ffffff
  290. ffff33
  291. ff33ff
  292. ff3333
  293. 33ffff
  294. 33ff33
  295. 3333ff
  296. 333333
  297. wwwwww
  298. UUUUUU
  299. DDDDDD
  300. """"""
  301. dddddd
  302. ff33@
  303. ffffff
  304. ffff33
  305. ff33ff
  306. ff3333
  307. 33ffff
  308. 33ff33
  309. 3333ff
  310. 333333
  311. wwwwww
  312. UUUUUU
  313. DDDDDD
  314. """"""
  315. dddddd
  316. ff33@
  317. ffffff
  318. ffff33
  319. ff33ff
  320. ff3333
  321. 33ffff
  322. 33ff33
  323. 3333ff
  324. 333333
  325. wwwwww
  326. UUUUUU
  327. DDDDDD
  328. """"""
  329. dddddd
  330. ff33@
  331. ffffff
  332. ffff33
  333. ff33ff
  334. ff3333
  335. 33ffff
  336. 33ff33
  337. 3333ff
  338. 333333
  339. wwwwww
  340. UUUUUU
  341. DDDDDD
  342. """"""
  343. dddddd
  344. ff33@
  345. ffffff
  346. ffff33
  347. ff33ff
  348. ff3333
  349. 33ffff
  350. 33ff33
  351. 3333ff
  352. 333333
  353. wwwwww
  354. UUUUUU
  355. DDDDDD
  356. """"""
  357. dddddd
  358. ff33@
  359. ffffff
  360. ffff33
  361. ff33ff
  362. ff3333
  363. 33ffff
  364. 33ff33
  365. 3333ff
  366. 333333
  367. wwwwww
  368. UUUUUU
  369. DDDDDD
  370. """"""
  371. Standard
  372. dddddd
  373. ff33@
  374. ffffff
  375. ffff33
  376. ff33ff
  377. ff3333
  378. 33ffff
  379. 33ff33
  380. 3333ff
  381. 333333
  382. wwwwww
  383. UUUUUU
  384. DDDDDD
  385. """"""
  386. dddddd
  387. ff33@
  388. ffffff
  389. ffff33
  390. ff33ff
  391. ff3333
  392. 33ffff
  393. 33ff33
  394. 3333ff
  395. 333333
  396. wwwwww
  397. UUUUUU
  398. DDDDDD
  399. """"""
  400. dddddd
  401. ff33@
  402. ffffff
  403. ffff33
  404. ff33ff
  405. ff3333
  406. 33ffff
  407. 33ff33
  408. 3333ff
  409. 333333
  410. wwwwww
  411. UUUUUU
  412. DDDDDD
  413. """"""
  414. dddddd
  415. ff33@
  416. ffffff
  417. ffff33
  418. ff33ff
  419. ff3333
  420. 33ffff
  421. 33ff33
  422. 3333ff
  423. 333333
  424. wwwwww
  425. UUUUUU
  426. DDDDDD
  427. """"""
  428. dddddd
  429. ff33@
  430. ffffff
  431. ffff33
  432. ff33ff
  433. ff3333
  434. 33ffff
  435. 33ff33
  436. 3333ff
  437. 333333
  438. wwwwww
  439. UUUUUU
  440. DDDDDD
  441. """"""
  442. dddddd
  443. ff33@
  444. ffffff
  445. ffff33
  446. ff33ff
  447. ff3333
  448. 33ffff
  449. 33ff33
  450. 3333ff
  451. 333333
  452. wwwwww
  453. UUUUUU
  454. DDDDDD
  455. """"""
  456. dddddd
  457. ff33@
  458. ffffff
  459. ffff33
  460. ff33ff
  461. ff3333
  462. 33ffff
  463. 33ff33
  464. 3333ff
  465. 333333
  466. wwwwww
  467. UUUUUU
  468. DDDDDD
  469. """"""
  470. dddddd
  471. ff33@
  472. ffffff
  473. ffff33
  474. ff33ff
  475. ff3333
  476. 33ffff
  477. 33ff33
  478. 3333ff
  479. 333333
  480. wwwwww
  481. UUUUUU
  482. DDDDDD
  483. """"""
  484. dddddd
  485. ff33@
  486. ffffff
  487. ffff33
  488. ff33ff
  489. ff3333
  490. 33ffff
  491. 33ff33
  492. 3333ff
  493. 333333
  494. wwwwww
  495. UUUUUU
  496. DDDDDD
  497. """"""
  498. dddddd
  499. ff33@
  500. ffffff
  501. ffff33
  502. ff33ff
  503. ff3333
  504. 33ffff
  505. 33ff33
  506. 3333ff
  507. 333333
  508. wwwwww
  509. UUUUUU
  510. DDDDDD
  511. """"""
  512. Standard
  513. dddddd
  514. ff33@
  515. ffffff
  516. ffff33
  517. ff33ff
  518. ff3333
  519. 33ffff
  520. 33ff33
  521. 3333ff
  522. 333333
  523. wwwwww
  524. UUUUUU
  525. DDDDDD
  526. """"""
  527. dddddd
  528. ff33@
  529. ffffff
  530. ffff33
  531. ff33ff
  532. ff3333
  533. 33ffff
  534. 33ff33
  535. 3333ff
  536. 333333
  537. wwwwww
  538. UUUUUU
  539. DDDDDD
  540. """"""
  541. dddddd
  542. ff33@
  543. ffffff
  544. ffff33
  545. ff33ff
  546. ff3333
  547. 33ffff
  548. 33ff33
  549. 3333ff
  550. 333333
  551. wwwwww
  552. UUUUUU
  553. DDDDDD
  554. """"""
  555. dddddd
  556. ff33@
  557. ffffff
  558. ffff33
  559. ff33ff
  560. ff3333
  561. 33ffff
  562. 33ff33
  563. 3333ff
  564. 333333
  565. wwwwww
  566. UUUUUU
  567. DDDDDD
  568. """"""
  569. dddddd
  570. ff33@
  571. ffffff
  572. ffff33
  573. ff33ff
  574. ff3333
  575. 33ffff
  576. 33ff33
  577. 3333ff
  578. 333333
  579. wwwwww
  580. UUUUUU
  581. DDDDDD
  582. """"""
  583. dddddd
  584. ff33@
  585. ffffff
  586. ffff33
  587. ff33ff
  588. ff3333
  589. 33ffff
  590. 33ff33
  591. 3333ff
  592. 333333
  593. wwwwww
  594. UUUUUU
  595. DDDDDD
  596. """"""
  597. dddddd
  598. ff33@
  599. ffffff
  600. ffff33
  601. ff33ff
  602. ff3333
  603. 33ffff
  604. 33ff33
  605. 3333ff
  606. 333333
  607. wwwwww
  608. UUUUUU
  609. DDDDDD
  610. """"""
  611. dddddd
  612. ff33@
  613. ffffff
  614. ffff33
  615. ff33ff
  616. ff3333
  617. 33ffff
  618. 33ff33
  619. 3333ff
  620. 333333
  621. wwwwww
  622. UUUUUU
  623. DDDDDD
  624. """"""
  625. dddddd
  626. ff33@
  627. ffffff
  628. ffff33
  629. ff33ff
  630. ff3333
  631. 33ffff
  632. 33ff33
  633. 3333ff
  634. 333333
  635. wwwwww
  636. UUUUUU
  637. DDDDDD
  638. """"""
  639. dddddd
  640. ff33@
  641. ffffff
  642. ffff33
  643. ff33ff
  644. ff3333
  645. 33ffff
  646. 33ff33
  647. 3333ff
  648. 333333
  649. wwwwww
  650. UUUUUU
  651. DDDDDD
  652. """"""
  653. dddddd
  654. ff33@
  655. ffffff
  656. ffff33
  657. ff33ff
  658. ff3333
  659. 33ffff
  660. 33ff33
  661. 3333ff
  662. 333333
  663. wwwwww
  664. UUUUUU
  665. DDDDDD
  666. """"""
  667. dddddd
  668. ff33@
  669. ffffff
  670. ffff33
  671. ff33ff
  672. ff3333
  673. 33ffff
  674. 33ff33
  675. 3333ff
  676. 333333
  677. wwwwww
  678. UUUUUU
  679. DDDDDD
  680. """"""
  681. dddddd
  682. ff33@
  683. ffffff
  684. ffff33
  685. ff33ff
  686. ff3333
  687. 33ffff
  688. 33ff33
  689. 3333ff
  690. 333333
  691. wwwwww
  692. UUUUUU
  693. DDDDDD
  694. """"""
  695. dddddd
  696. ff33@
  697. ffffff
  698. ffff33
  699. ff33ff
  700. ff3333
  701. 33ffff
  702. 33ff33
  703. 3333ff
  704. 333333
  705. wwwwww
  706. UUUUUU
  707. DDDDDD
  708. """"""
  709. dddddd
  710. ff33@
  711. ffffff
  712. ffff33
  713. ff33ff
  714. ff3333
  715. 33ffff
  716. 33ff33
  717. 3333ff
  718. 333333
  719. wwwwww
  720. UUUUUU
  721. DDDDDD
  722. """"""
  723. dddddd
  724. ff33@
  725. ffffff
  726. ffff33
  727. ff33ff
  728. ff3333
  729. 33ffff
  730. 33ff33
  731. 3333ff
  732. 333333
  733. wwwwww
  734. UUUUUU
  735. DDDDDD
  736. """"""
  737. dddddd
  738. ff33@
  739. ffffff
  740. ffff33
  741. ff33ff
  742. ff3333
  743. 33ffff
  744. 33ff33
  745. 3333ff
  746. 333333
  747. wwwwww
  748. UUUUUU
  749. DDDDDD
  750. """"""
  751. dddddd
  752. ff33@
  753. ffffff
  754. ffff33
  755. ff33ff
  756. ff3333
  757. 33ffff
  758. 33ff33
  759. 3333ff
  760. 333333
  761. wwwwww
  762. UUUUUU
  763. DDDDDD
  764. """"""
  765. Standard
  766. dddddd
  767. ff33@
  768. ffffff
  769. ffff33
  770. ff33ff
  771. ff3333
  772. 33ffff
  773. 33ff33
  774. 3333ff
  775. 333333
  776. wwwwww
  777. UUUUUU
  778. DDDDDD
  779. """"""
  780. dddddd
  781. ff33@
  782. ffffff
  783. ffff33
  784. ff33ff
  785. ff3333
  786. 33ffff
  787. 33ff33
  788. 3333ff
  789. 333333
  790. wwwwww
  791. UUUUUU
  792. DDDDDD
  793. """"""
  794. dddddd
  795. ff33@
  796. ffffff
  797. ffff33
  798. ff33ff
  799. ff3333
  800. 33ffff
  801. 33ff33
  802. 3333ff
  803. 333333
  804. wwwwww
  805. UUUUUU
  806. DDDDDD
  807. """"""
  808. dddddd
  809. ff33@
  810. ffffff
  811. ffff33
  812. ff33ff
  813. ff3333
  814. 33ffff
  815. 33ff33
  816. 3333ff
  817. 333333
  818. wwwwww
  819. UUUUUU
  820. DDDDDD
  821. """"""
  822. Header2
  823. Header2End
  824. Standard
  825. HeaderEnd
  826. Header2
  827. Header2End
  828. Standard
  829. Standard
  830. Header2
  831. Header2End
  832. Standard
  833. Standard
  834. before setting the
  835. breakpoint
  836. after setting the
  837. breakpoint
  838. instr i-1
  839. instr i
  840. instr i+1
  841. instr i-1
  842. instr i+1
  843. breakpoint =>
  844. breakpoint =>
  845. buffer
  846. instr i
  847. Palatino
  848. before setting the
  849. breakpoint(
  850. after setting the
  851. breakpoint(
  852. instr i-1
  853. instr i
  854. instr i+1
  855. instr i-1
  856. instr i+1
  857. breakpoint =>(
  858. breakpoint =>(
  859. buffer*
  860. instr i0
  861. Standard
  862. Header3
  863. Standard
  864. KeplerElems
  865. Alloc
  866. KeplerGraphs
  867. GraphDesc
  868. KeplerGraphs
  869. StarDesc
  870. Kepler2
  871. OffsetDesc
  872. KeplerGraphs
  873. ConsDesc
  874. KeplerFrames
  875. CaptionDesc
  876. Trap handler
  877. Syntax10.Scn.Fnt
  878. Debug mode
  879. Syntax10.Scn.Fnt
  880. Kepler7
  881. TextDesc
  882. Syntax10.Scn.Fnt
  883. Standard mode
  884. Kepler1
  885. AttrDesc
  886. Kepler8
  887. FilledCircleDesc
  888. Syntax10.Scn.Fnt
  889. Breakpoint
  890. Syntax10.Scn.Fnt
  891. Breakpoint
  892. Traps
  893. Syntax10.Scn.Fnt
  894. Context switches
  895. Syntax10.Scn.Fnt
  896. RTD.Step
  897. Syntax10.Scn.Fnt
  898. RTD.Step
  899. Syntax10.Scn.Fnt
  900. KeplerGraphs
  901. GraphDesc
  902. KeplerGraphs
  903. StarDesc
  904. Kepler2
  905. OffsetDesc
  906. KeplerGraphs
  907. ConsDesc
  908. Kepler7
  909. TextDesc
  910. Syntax10.Scn.Fnt
  911. instr i-1
  912. instr i+1
  913. Syntax10.Scn.Fnt
  914. breakpoint =>
  915. KeplerFrames
  916. CaptionDesc
  917. save area
  918. Syntax10.Scn.Fnt
  919. instr i
  920. Syntax10.Scn.Fnt
  921. Syntax10.Scn.Fnt
  922. Kepler1
  923. RectangleDesc
  924. Kepler8
  925. AttrRectDesc
  926. Kepler1
  927. LineDesc
  928.     Kepler1
  929. AttrDesc
  930. bc save area[2]
  931. save area[0]
  932. save area[1]
  933. save area[2]
  934. b target
  935.     bc target
  936. instr i
  937. b target
  938. b instr (i+1)
  939. other
  940.     instr   i
  941. b instr (i+1)
  942. b target
  943. LR:=ADR(instr (i+1))
  944. Palatino
  945. bc save area[2](
  946. save area[0]*
  947. save area[1]*
  948. save area[2])]
  949. b target(
  950. u    bc target(
  951. instr i)
  952. b target(
  953. b instr (i+1)(
  954. other(
  955. 9    instr   i*
  956. b instr (i+1)(
  957. b target(
  958. LR:=ADR(instr (i+1))0
  959. Header2
  960. Header2End
  961. Standard
  962. Effective Address
  963. Value
  964. Dynamic Type
  965. Static Type
  966. Offset
  967. Compiler
  968. System State
  969. Base Address
  970. Palatino
  971. Effective Address+?D
  972. Value(
  973. Dynamic Type(
  974. Static Type(
  975. Offset(
  976. Compiler(
  977. System State(
  978. Base Address
  979. Header2
  980. Header2End
  981. Standard
  982. Header3
  983. Standard
  984. Header3
  985. Standard
  986. Standard
  987. HeaderEnd
  988. Standard
  989. Standard
  990. Standard
  991. Standard
  992. Header2
  993. KeplerGraphs
  994. GraphDesc
  995. KeplerGraphs
  996. StarDesc
  997. Kepler1
  998. RectangleDesc
  999. KeplerFrames
  1000. CaptionDesc
  1001. Syntax10.Scn.Fnt
  1002. Syntax10.Scn.Fnt
  1003. Syntax10.Scn.Fnt
  1004. Syntax10.Scn.Fnt
  1005. Syntax10.Scn.Fnt
  1006. Kepler1
  1007. AttrDesc
  1008. Standard
  1009. Header3
  1010. Header3
  1011. Standard
  1012. Header3
  1013. Header2
  1014. Standard
  1015. Header3
  1016. Header3
  1017. Header2
  1018. Standard
  1019. Header3
  1020. Header2
  1021. Header3
  1022. Standard
  1023. HeaderEnd
  1024. Standard
  1025. Header1
  1026. Abstract
  1027. The Oberon environment [Wir89] offers only limited possibilities for inspecting run time data and for determining the cause for an exception. Only variables of basic types such as INTEGER or CHAR can be examined. It is not possible to execute a program step by step.
  1028. This report describes a run time debugger that allows the inspection of structured types such as RECORD or ARRAY as well as step by step execution. The debugger supports views on local and global variables of any type. Run time types are supported as well as dynamic arrays. It is possible to follow pointers in order to traverse complex data structures. The debugger supports single stepping as well as breakpoints.
  1029. Another goal was to embed the debugger into the Oberon environment as smoothly as possible. This results in a look and feel typical for Oberon. Many features of the Oberon system (text frames, text elements) have been reused, resulting in small and compact code. The run time debugger was implemented for PowerMac Oberon.
  1030. Keywords:    Programming techniques, Testing and Debugging; Programming Environments Operating Systems, Systems Programs and Utilities
  1031. Contents
  1032. 1. Introduction
  1033. 2. How to Use the Debugger
  1034.     2.1 An Example
  1035.     2.2 Commands
  1036.     2.3 Data Viewers
  1037.     2.4 Limitations
  1038. 3. Implementation
  1039.     3.1 Compiler support
  1040.     3.2 Stepwise execution
  1041.         3.2.1 Patching
  1042.         3.2.2 Context switch
  1043.     3.3 Determine values of variables
  1044.     3.4 User interface
  1045.         3.4.1 Source Viewers
  1046.         3.4.2 Data Viewers
  1047. 4. Extensibility
  1048.     4.1 Module hierarchy
  1049.     4.2 RTDT (low-level Trap handling, context switches)
  1050.     4.3 RTDB (Breakpoint handling)
  1051.     4.4 RTDC (Compiler Interface)
  1052.     4.5 RTDD (Data viewers)
  1053. 5. Conclusions
  1054. 6. References
  1055. 1. Introduction
  1056. A major drawback of the Oberon system is its lack of a debugger. In Oberon there are only three means for getting information about a running program: 
  1057.     The command System.State (showing part of the global variables of a module).
  1058.     The command System.ShowModules (showing the list of all loaded modules).
  1059.     The trap viewer (showing the active procedures on the stack as well as part of their variables).
  1060. One of the problems for successful debugging is buried within the words 'part of'. Only variables, for which there exists reference information in the object module, are shown. This reference information is created by the compiler. Unfortunately, the compiler does not generate this information for all variables. Structured types such as arrays or records are omitted. Therefore variables of these types cannot be shown. Pointers can only be shown as the address of the object they reference.
  1061. To circumvent these problems a post mortem debugger was implemented as a first step [Hof94].  This tool displays the following information:
  1062.     Global and local variables of all modules and active procedures regardless of their types.  
  1063.     The source code position of the program counters for all active procedures on the stack.
  1064. Additionally some general design goals were set, which partially contradict each other. The main objective was to find an optimal balance between the different goals:
  1065.     As simple as possible.
  1066.     Minimal use of memory.
  1067.     No interference with normal work. No additional delays.
  1068.     Conformity with the Oberon environment and usage conventions. User interface with commands, viewers and text elements.
  1069.     No modifications of the Oberon system and the Oberon compiler which are not absolutely necessary.
  1070. These goals were met to a large degree. The post mortem debugger needed almost no memory on the Oberon heap, only one minor change in the compiler, and was built on top of the Oberon environment using text elements as well as viewers. As a result of making it as simple as possible, it needed only about 40 kBytes of disk space. 
  1071. Daily usage in research as well as in teaching showed, that there was still some need for a more advanced debugging tool. This led to the development of the run time debugger presented in this paper. The run time debugger meets the same design goals as the post mortem debugger. Additionally it offers the following new features:
  1072.     Step by step execution of a program.
  1073.     Setting of breakpoints.
  1074.     Views on variables updated automatically after every debugging step.
  1075.     Reuse of parts of the post mortem debugger.
  1076. 2. How to Use the Debugger
  1077. We first explain the usage of the debugger with an example. Then we describe its commands and its other abilities in depth.
  1078. 2.1 An Example
  1079. Consider the following sample program:
  1080. MODULE Demo;
  1081.     IMPORT Out;
  1082.     PROCEDURE Do*;
  1083.         VAR i: INTEGER; arr: ARRAY 3 OF INTEGER;
  1084.     BEGIN
  1085.         Out.String ("Hello world$");
  1086.         FOR i := 0 TO 2 DO
  1087.             arr[i] := i*2;
  1088.             Out.String ("Hello again$")
  1089.         END
  1090.     END Do;
  1091. END Demo.
  1092. To start debugging, the debugger has to know which modules should be traced by the debugger. In our case we only want to trace the module Demo.
  1093. Debug.Trace Demo ~
  1094. After running this command everything is prepared. Debugging is started automatically upon entering one of the marked modules (here Demo). In our example we enter the traced code by starting the command Demo.Do with a click on the middle mouse button. After a traced module has been activated, execution is suspended and a viewer is opened showing the source text corresponding to the current program counter (PC). The exact position of the PC is marked with a special text element:
  1095. MODULE Demo;
  1096.     IMPORT Out;
  1097.     PROCEDURE Do*;
  1098.         VAR i: INTEGER; arr: ARRAY 3 OF INTEGER;
  1099.     BEGIN
  1100.         Out.String ("Hello world$");
  1101.         FOR i := 0 TO 4 DO
  1102.             arr[i] := i*2;
  1103.             Out.String ("Hello again$")
  1104.         END
  1105.     END Do;
  1106. END Demo.
  1107. The program may now be executed step by step by using the command Debug.Step. Alternatively, it can be executed up to the next breakpoint with Debug.Run. With Debug.Data Demo.Do one can open a so called data viewer. A data viewer always displays the variables of a procedure or module together with their current values. In this case it displays the values of i and arr. If one would open a data viewer of Demo.Do in the above situation, the values of i and arr were not defined. After stepping through some statements, one gets to the following state:
  1108. MODULE Demo;
  1109.     IMPORT Out;
  1110.     PROCEDURE Do*;
  1111.         VAR i: INTEGER; arr: ARRAY 3 OF INTEGER;
  1112.     BEGIN
  1113.         Out.String ("Hello world$");
  1114.         FOR i := 0 TO 2 DO
  1115.             arr[i] := i*2
  1116.             Out.String ("Hello again$")
  1117.         END
  1118.     END Do;
  1119. END Demo.
  1120. From step to step, the data viewer is automatically updated, to show the current values of the variables. This results in the following display of the variables of Demo.Do in the data viewer:
  1121. arr = 
  1122.     0 = 0
  1123.     1 = 2
  1124.     2 = 4 
  1125. i = 2
  1126. The components of the array arr are enclosed in so-called fold elements (opening and closing triangles) [MoK95]. By middle clicking on one of the triangles, one can collapse the text between these elements (giving 
  1127.  instead of
  1128. ). By default, fold elements are closed to avoid long data viewers which tend to be difficult to inspect (Fold elements are distributed with the standard Oberon environment).
  1129. Instead of the command interface described above, one may also use the Dialogs package [Kna94] as a means to communicate with the debugger (Figure 1).
  1130. Figure 1: Debugger Dialog
  1131. 2.2 Commands
  1132. Like other Oberon tools, the debugger is not a program for itself, but a collection of modules which export several commands. There are two types of commands:
  1133.     Initialisation commands define the state of the debugger.
  1134.     Debugging commands change or give information about the currently debugged program.
  1135. Initialisation Commands
  1136.     Debug.Trace {module}. Registers the modules that are to be traced. When a module has been registered, execution halts either when one of its statements is reached in single step mode or when a breakpoint in this module is encountered. Note that it is possible to selectively trace individual modules of a system.
  1137.     Debug.Close: Ends the current debugging session. The allocated memory is freed and the debugged modules are restored to their former state.
  1138.     Debug.ShowModules: Shows the set of currently registered modules.
  1139.     Debug.PostMortem: Installs the debuggers Post Mortem facility. The machine state of a later trap may then be inspected as if a debugging step has been executed.
  1140. Debugging Commands
  1141.     Debug.StepInto: Executes the next statement after the PC position. If this statement calls a procedure of a registered module, execution is stopped before the first statement of the procedure (step into mode). 
  1142.     Debug.Step: Executes the next statement after the PC position. If this statement calls a procedure, this procedure is not debugged but executed completely, even if it is in a registered module (step over mode). However, an encountered breakpoint inside of the procedure will cause a program stop.
  1143.     Debug.Breakpoint: Sets a breakpoint in front of the statement containing the caret. The breakpoint is shown as 
  1144. . During debugging, an encountered breakpoint triggers a program stop.
  1145.     Debug.Run: Executes the debugged program until a breakpoint is encountered or the end of the program is reached (i.e. the command returns to the Oberon loop).
  1146.     Debug.Data (module | procedure | ^): Opens a data viewer and shows all variables of the specified module or procedure (if that procedure has an active frame on the current stack). Note that it is also possible to inspect the global data of a module which is not registered.
  1147.     Debug.Return: Executes the debugged program until the current procedure returns to its caller. However, execution will be stopped, if a user-defined breakpoint is encountered.
  1148.     Debug.Source (procedure): Shows the source code of the specified procedure and sets the caret to the current position within this procedure. The procedure must have an active frame on the stack. This is useful for determining the exact halt position when the debugger is used in post mortem mode.
  1149.     Debug.Stack: Displays a list of procedures having an active frame on the stack. After a trap these are the procedures that were active when the trap occurred.
  1150. 2.3 Data Viewers
  1151. Data viewers display the values of local, global or heap variables. They are opened with the command Debug.Data. A data viewer is a normal text viewer. All commands applicable to text viewers are also valid for data viewers. 
  1152. Variables of basic types, strings, procedure variables and NIL-pointers are displayed with their respective names and values. For example:
  1153. i = 100
  1154. ch = 'C'
  1155. str = "a string"
  1156. real = 3.14159265D+000
  1157. bool = TRUE
  1158. set = {3, 17}
  1159. proc = Texts.Notify
  1160. ptr = NIL
  1161. Variables of structured types (arrays, records) or pointers are displayed with their names and a pair of fold elements which can be expanded to show the components of these types. For example:
  1162. ptr^ 
  1163. Clicking on one of the triangles shows the components of the corresponding variable. For example, clicking on the fold element after 'arr' leads to:
  1164. ptr^ 
  1165.     0 = 17
  1166.     1 = 3
  1167.     2 = 25 
  1168. Nested structured types are displayed as nested fold elements. For example, a record with two fields of array type is displayed as:
  1169.     arr1 
  1170.     arr2 
  1171.           0 = 41
  1172.           1 = 35 
  1173. ptr^ 
  1174. Data structures linked via pointers are displayed with nested fold elements as well. For example:
  1175. ptr^ 
  1176.     data 
  1177.     next^ 
  1178.         data 
  1179.         next^ 
  1180.             data 
  1181.             next^ 
  1182. A record which is an extension of another record is displayed with fold elements for its base type. For example:
  1183.     f1 = 3
  1184.     f2 = -17 
  1185. 2.4 Limitations
  1186. There are some limitations inherent to the structure of the debugger (see also Section 3):
  1187.     It is only possible to debug modules, whose source code is available.
  1188.     In order to use as little memory as possible, the state of the debugged modules is not saved completely. Therefore, modifying the global state of the debugged modules by commands executed between two debugging steps is potentially dangerous. However, commands not related to the debugged modules may be executed without any special considerations.
  1189.     Since a module is loaded into memory as soon as it is registered, the body of a module cannot be debugged. 
  1190. 3. Implementation
  1191. The implementation of the debugger consists roughly of three parts. The first part handles the stepwise execution, the second extracts the actual values of variables, and the third part presents the information generated by the other two parts to the user. Each part will be described in its own section. But first, some low level information is presented.
  1192. 3.1 Compiler support
  1193. The debugger mainly does two things: Stepping through a program and displaying the values of variables. To achieve this, it needs information on how to interpret the memory (heap and stack), i.e., it needs the types and addresses of global and local variables, as well as information about statement boundaries to allow stepwise execution. Most debuggers get this information from special files created by the compiler (so called reference files). This has several disadvantages:
  1194.     For every compiled module an additional file is needed, even if a module is never debugged.
  1195.     The compiler has to be modified in order to create these files.
  1196.     The debugger has to read these files and to build a data structure similar to the symbol table built by the compiler.
  1197. To circumvent these problems another approach was chosen. The idea was to create the reference information of a module on demand by compiling the module and using the symbol table directly from the compiler. This needs only a minor modification of the compiler. Most of the above problems are avoided, but there are also some disadvantages:
  1198.     There is a slight delay when accessing debug information of a module, since the module has to be recompiled first.
  1199.     Problems may arise, if the source code of a module is modified after it has been loaded by the Oberon system. The position of the current program counter may be wrong, as its position is still calculated correspondingly to the older source code. However, debuggers using reference files have this problem as well.
  1200. The delay for recompiling a module is so short, that it is only noticeable on slow machines (The PowerMac Oberon compiler compiles approx. 2000 lines per second). In addition, the debugger maintains a cache for the debug information of the most recently used modules. The modifications to the compiler are negligible. There are only two necessary changes:
  1201.     A pointer to the symbol table must be stored in a global variable in order to prevent the garbage collector from freeing this memory. This can be done in a single line.
  1202.     A table must be generated that relates statement boundaries to PC values and vice versa. This results in another 10 lines added to the compiler. 
  1203. 3.2 Stepwise execution
  1204. Issuing one of the step commands results in the following actions:
  1205.     The code is patched with trap instructions at all statement boundaries.
  1206.     The context is switched to the debugged program.
  1207.     After a patched trap instruction was reached, the debug context is saved.
  1208.     Control is given back to the standard Oberon loop.
  1209. 3.2.1 Patching
  1210. In order to stop execution after a debugging step, trap instructions are inserted into the code segment of the debugged modules. These instructions replace the first machine code instructions of all possibly following Oberon statements. Overwritten machine instructions are saved to a buffer in order to be able to restore them later on (Figure 2).
  1211. Figure 2: Patching of instruction i
  1212. Depending on the chosen step command, the set of following statements differs. Therefore not all statement boundaries are patched with trap instructions. 
  1213.     Debug.StepInto inserts trap instructions at all statement boundaries reported by the compiler. It would be possible to scan the machine instructions to restrict the number of statements, but 
  1214.     Debug.Step inserts trap instructions in all active procedures as well as at all breakpoint positions.
  1215.     Debug.Run inserts trap instructions at all breakpoint positions.
  1216.     Debug.Return inserts trap instructions in all active procedures as well as at all breakpoint positions except for the current procedure on the bottom of the stack..
  1217. 3.2.2 Context switch
  1218. There are two kinds of context switches. When the debugged program runs into a trap instruction, control is transferred to the Oberon loop (standard mode). When the user issues a debbuger command such as Debug.Step, control is transferred back to the debugged program which is then running in debug mode again. Both context switches are initiated by traps and are performed in the trap handler (Figure 3).
  1219.       
  1220. Figure 3: Two sample debugging steps
  1221.     Debug mode to standard mode: The debugged program runs into a trap instruction (breakpoint). Before control can be tranferred to the Oberon system, the debugger has to save information about the debugged program (stack and registers) and to update the views visible to the user. The update is not done directly in the context switch, but through a more general mechanism, in order to allow later addition of further extensions to the debugger (see also Section 4).
  1222.     Standard mode to debug mode: This context switch is generated explicitly through the step commands activated by the user. After patching the code with trap instructions (see above), the step command issues a trap to trigger the context switch. Before the actual context switch takes place, the trap handler makes an upcall to the user interface to allow the views to prepare themselves for the next debugging step. Then the trap handler restores the state of the debugged program (stack and registers) and resumes execution at the address where the latest trap occurred. As there may be a trap instruction at this address, execution is resumed in a separate memory location called 'save area' (Figure 4).
  1223. Figure 4: Launching of a debug step
  1224. In principle, this area contains two machine instructions: the instruction hidden by the trap instruction and a branch to the instruction following the trap instruction. If the hidden instruction is a relative branch, its target address has to be modified. There are three different cases to be considered (see Figure 5):
  1225.     relative branch conditional (bc)
  1226.     relative branch unconditional (b), used when a procedure is called
  1227.     other instructions
  1228. Figure 5: Structure of the save area depending on the kind of the saved instruction
  1229. By moving a conditional branch instruction to the save area, its branch distance may exceed the allowable limit. Therefore an indirection through an unconditional branch located in save area[2] is introduced. An unconditional branch overwritten by a trap instruction is typically a procedure call. In order to return correctly from the called procedure, the link register (LR) is set to the instruction following the trap instruction
  1230. 3.3 Getting the values of variables
  1231. To display a variable with its actual value, the debugger needs the following information
  1232.     the effective address of the variable
  1233.     the variable's actual run time type
  1234. The effective address can be calculated from the information provided by the compiler (offset of the variable relative to the base address of the corresponding module or procedure) and the actual base address. If the static type of a variable is a record, the dynamic type may be an extension of it. The dynamic type can be obtained from the record's type descriptor whose address is stored near the effective address of the record. From the address of a variable (and possibly its dynamic type) the value of the variable can be computed (Figure 6).
  1235. Figure 6: Determine value and run time type of variables
  1236. 3.4 User interface
  1237. We set two main goals for the user interface:
  1238.     The debugger should have an Oberon-like 'look and feel'
  1239.     The user interface should be extensible
  1240. The main idea was to start with a simple and small user interface which may later be extended without changing the debugger (for details see Section 4). The minimal user interface consists of two types of viewers. Source viewers displaying the control flow and data viewers showing the current values of variables. Both views are automatically updated after each debugging step.
  1241. 3.4.1 Source Viewers
  1242. Source viewers are standard text viewers. They are opened automatically by the debugger but can also be opened by the user with Edit.Open. To achieve the added functionality, HandlerElems are used (for further information read the file Elem.Guide.Text of the Oberon system). After every debugging step a SetPC message is broadcast. This message contains the name of the module as well as the text position corresponding to the current PC. Upon receiving this message, a text frame displaying the named source text inserts a PC element at the indicated text position and sets a flag in the message. After the broadcast this flag is tested. If it is set, no further action is taken. Otherwise a new viewer is opened showing the desired source text and a PC element is inserted at the appropriate position.
  1243. 3.4.2 Data Viewers
  1244. Data viewers are normal text viewers displaying all variables of a module or a procedure. Fold elements and indentation are used to enhance readability. After every debugging step, the shown values are updated automatically. A view on the data of a no longer active procedure (no active stack frame) or an unloaded module is marked.
  1245. 4. Extensibility
  1246. The user interface of the debugger consists of two parts. On the one hand there is a collection of user-startable actions (commands) and on the other hand there is a set of actions, invoked automatically by the debugger at the beginning and the end of each debugging step. One may use the commands either directly by middle-clicking on them or indirectly through a dialog.
  1247. The interface of the debugger is extensible in two ways. First, one can add new commands or dialogs (extensibility inherent to the Oberon system). Second, it is possible to add arbitrary actions that are then activated after every debugging step. In principle, one can add any new or improved feature to the debugger (e.g. a graphical representation of the current object hierarchy). If a procedure named MyGraphicHandler should be activated after every debugging step, one has to call
  1248. RTDT.debugQ.Add (MyGraphicHandler)
  1249. If a procedure name MyCleanUp should be called before every debugging step, one has to call
  1250. RTDT.startQ.Add (MyCleanUp)
  1251. Currently, there are two installed actions executed after every debugging step (one updates the source viewers and the other updates the data viewers) and one action executed before every debugging step (it deletes the current PC element in the source viewers).
  1252. The debugger modules offer several auxiliary procedures which can be used by new extensions. The following sections describe each module's interface, as far as they are important for future extensions.
  1253. 4.1 Module hierarchy
  1254. 4.2 RTDT (low-level Trap handling, context switches)
  1255. DEFINITION RTDT;
  1256.     CONST
  1257.         EnterDebugMode = 255;    
  1258.     TYPE
  1259.         Proc = POINTER TO ProcDesc;
  1260.         ProcDesc = RECORD
  1261.             up: Proc;                    
  1262.             pc, sp: LONGINT;                
  1263.             name: ARRAY 64 OF CHAR;    
  1264.             modName: ARRAY 32 OF CHAR; 
  1265.             regs: Sys.ExceptionInfo;        
  1266.             beginPC, endPC: LONGINT;    
  1267.         END ;
  1268.         debugQ-: Kernel.Queue;
  1269.         startQ-: Kernel.Queue;
  1270.         procs-: Proc;
  1271.     PROCEDURE Debugging (): BOOLEAN;
  1272.     PROCEDURE FindProc (startPC: LONGINT; VAR name: ARRAY OF CHAR);
  1273.     PROCEDURE Launching (): BOOLEAN;
  1274.     PROCEDURE PC (): LONGINT;
  1275.     PROCEDURE PopProc;
  1276.     PROCEDURE SearchProc (pc: LONGINT; VAR mod: Modules.Module;
  1277.                                     VAR refpos, refend, startpc, endpc: LONGINT);
  1278. END RTDT.
  1279. Constants 
  1280.     EnterDebugMode is the trap number used to initiate a context switch to the debug mode. To write an own command which initiates a debugging step, set the desired breakpoints and call HALT(EnterDebugMode) in order to resume the execution of the debugged modules.
  1281. Types 
  1282.     ProcDesc represents a procedure with an activation frame on the debugging stack. It contains the following information:
  1283.     up is a link to the procedure's caller.
  1284.     pc is the address of the latest executed instruction (of this procedure).
  1285.     sp is the procedure's stack pointer.
  1286.     name is the procedure's name
  1287.     modName is the name of the module containing the procedure.
  1288.     regs are the procedure's registers.
  1289.     beginPC and endPC define the address and size of the procedure's code in memory.
  1290. Global variables
  1291.     debugQ: Procedures registered in debugQ are called whenever a debugging step has finished (e.g. useful to update information on the screen).
  1292.     startQ: Procedures registered in startQ are called whenever a debugging step is about to be started (e.g. to remove temporary information visible on screen).
  1293.     procs: Points to the list of procedures currently on the debugging stack.
  1294. Operations 
  1295.     Debugging () returns TRUE if a module is currently debugged.
  1296.     FindProc (startPC, name) returns the name of the procedure starting at the address startPC.
  1297.     Launching () returns TRUE if modules have been registered for debugging but have not yet been entered, i. e. there exists no saved state of the debugged modules.
  1298.     PC () returns the program counter at the end of the latest debugging step.
  1299.     PopProc removes the bottom most activation frame from the debugging stack.
  1300.     SearchProc (pc, mod, refStart, refEnd, startPC, endPC) returns information about the procedure which contains the address pc. refStart and refEnd define the address and size of the procedure's reference information and startPC and endPC the address and size of its code.
  1301. 4.3 RTDB (Breakpoint handling)
  1302. DEFINITION RTDB;
  1303.     TYPE
  1304.         GetBPMsg = RECORD (Display.FrameMsg) END ;
  1305.         ModuleInfo = POINTER TO ModuleInfoDesc;
  1306.         ModuleInfoDesc = RECORD
  1307.             next-: ModuleInfo;
  1308.             name-: ARRAY 32 OF CHAR;
  1309.         END ;
  1310.         modules-: ModuleInfo;
  1311.     PROCEDURE AddModules (s: Texts.Scanner);
  1312.     PROCEDURE BreakAll;
  1313.     PROCEDURE BreakAtPC (VAR name: ARRAY OF CHAR; pos: LONGINT): BOOLEAN;
  1314.     PROCEDURE CleanUp;
  1315.     PROCEDURE EntryAll;
  1316.     PROCEDURE PCToPos (pc: LONGINT; VAR name: ARRAY OF CHAR;
  1317.                                 VAR pos: LONGINT);
  1318.     PROCEDURE PosToPC (VAR name: ARRAY OF CHAR; pos: LONGINT;
  1319.                                 VAR pc: LONGINT);
  1320.     PROCEDURE RestoreAll;
  1321.     PROCEDURE StepAll;
  1322.     PROCEDURE StepOverAll;
  1323. END RTDB.
  1324. Types 
  1325.     A GetBPMsg is broadcast in order to collect user defined breakpoints. Upon receiving this message, a handler of a text frame with breakpoints has to register them with help of the operation BreakAtPC. 
  1326. Global variables 
  1327.     modules points to a list of all debugged modules.
  1328. Operations 
  1329.     AddModules (s) reads names using the scanner s as long as they are valid. Each name is treated as the name of a module, which is then entered into the list of debugged modules.
  1330.     BreakAll inserts trap instructions for user-defined breakpoints in all debugged modules. Trap instructions for stepwise execution are previously removed.
  1331.     BreakAtPC (name, pos) inserts a trap instruction for the user-defined breakpoint in module name at text position pos. Should always be called upon receiving a GetBPMsg.
  1332.     CleanUp removes all patches in the debugged modules and clears the list of debugged modules.
  1333.     EntryAll inserts trap instructions at all entry points of all debugged modules. 
  1334.     RestoreAll removes all patches in the debugged modules.
  1335.     StepAll inserts trap instructions at all statement boundaries in all debugged modules.
  1336.     StepOverAll inserts trap instructions in all procedures with an activation frame on the debugging stack. 
  1337.     PCToPos (pc, name, pos) returns the module name and the text position corresponding to the address pc.
  1338.     PosToPC (name, pos, pc) returns in pc the code address corresponding to the text position pos in the module name.
  1339. 4.4 RTDC (Compiler Interface)
  1340. DEFINITION RTDC;
  1341.     TYPE
  1342.         ScanProc = PROCEDURE (obj: POPT.Object);
  1343.         Stat = RECORD
  1344.             pc-: POINTER TO ARRAY OF SHORTINT;
  1345.             pos-: POINTER TO ARRAY OF LONGINT;
  1346.         END ;
  1347.         Sym = POPT.Object;
  1348.         Type = POPT.Struct;
  1349.     PROCEDURE FindProc (proc: RTDT.Proc): Sym;
  1350.     PROCEDURE FindType (type: Types.Type; module: Modules.Module): Sym;
  1351.     PROCEDURE ScanScope (scope: Sym; proc: ScanProc);
  1352.     PROCEDURE Statements (name: ARRAY OF CHAR; VAR stats: Stat);
  1353.     PROCEDURE Symbols (name: ARRAY OF CHAR; VAR syms: Sym);
  1354. END RTDC.
  1355. Types 
  1356.     Stat contains two open arrays containing the statement boundaries as code addresses and as text positions. These arrays are used for translating code addresses to text positions and vice versa. The text position pos[i] corresponds to the code address 4*Sum (pc[0]..pc[i]). 
  1357.     Sym denotes an Oberon symbol (variable, procedure).
  1358.     Type denotes a type definition as given by the compiler.
  1359. Operations 
  1360.     FindProc (proc) returns the symbol information for the procedure proc.
  1361.     FindType (type, module) returns the symbol information for a given type. If its module's source code is not accessible, the information is searched in the module module.
  1362.     ScanScope (scope, proc) calls the procedure proc for all local objects of the procedure or module scope.
  1363.     Statements (name, stats) retrieves the statement boundaries for the module name. If they could not be determined, stats is NIL.
  1364.     Symbols (name, syms) retrieves the symbol information for the module name. If an error occurs, syms is NIL.
  1365. 4.5 RTDD (Data viewers)
  1366. DEFINITION RTDD;
  1367.     PROCEDURE GetLocalScope (VAR w: Texts.Writer; t: Texts.Text; syms: POPT.Object;
  1368.                                         reg: Sys.ExceptionInfo; indent: INTEGER);
  1369.     PROCEDURE GetScope (VAR w: Texts.Writer; t: Texts.Text; syms: POPT.Object;
  1370.                                     baseAdr: LONGINT; indent: INTEGER);
  1371. END RTDD.
  1372. Operations 
  1373.     GetLocalScope (w, t, syms, reg, indent) writes all local objects of a procedure to the writer w using the given indentation. The procedure is defined by its symbols syms and the register set reg. When a structured type is encountered (use of fold elements), the text t is scanned for the corresponding fold element. If it is found and it is open, it is automatically expanded when written to w. Therefore a fold element in a data viewer stays open, if a step command is executed.
  1374.     GetScope (w, t, syms, baseAdr, indent) writes all local objects of a module to the writer w using the given indentation. The module is defined by its symbols syms and the base address baseAdr. When a structured type is encountered (use of fold elements), the text t is scanned for the corresponding fold element. If it is found and it is open, it is automatically expanded when written to w. Therefore a fold element in a data viewer stays open, if a step command is executed.
  1375. 5. Conclusions
  1376. The strength of our debugger stems from its concepts being based on the Oberon environment. The debugger has the following main features:
  1377.     It needs no reference files.
  1378.     It is small and efficient by reusing many features of the Oberon system (the total object code size is about 30 kBytes).
  1379.     It fully supports the Oberon concept of multiple entry points into an application.
  1380.     It is extensible.
  1381. Context switches in general and hand-made code pieces in particular are highly system-dependent and processor-dependent. The debugger is currently implemented for the Power PC. This implies a high degree of non portability. However porting it to a processor with an architecture similar to the Power PC should not be too hard and time consuming. 
  1382. 6. References
  1383. [Ebe87]    Hans Eberle: Development and Analysis of a Workstation Computer. PhD thesis, Swiss Federal Institute of Technology (ETH Z
  1384. rich), 1987. Number 8431.
  1385. [Hof94]    Markus Hof: Post Mortem Debugger for Oberon. Proc. 1994 Joint Modular Languages Conference.
  1386. [Kna94]    Markus Knasm
  1387. ller: Oberon Dialogs: User's Guide and Programming Interfaces. Institute for computer science (system software), University of Linz, Report No. 1, November 1994.
  1388. [MoK95]    H.M
  1389. ssenb
  1390. ck, K.Koskimies: Active Texts for Structuring and Understanding Source Code. Paper submitted to Software 
  1391.  Practice and Experience.
  1392. [Wir89]    N. Wirth, J. Gutknecht: The Oberon System. Software-Practice and Experience, 19(9), 1989, 857-893.
  1393.